In this project, we will be visualizing data on economic statistics by country. These statistics include: Inequality, Inflation, Poverty, Wage Gap, Social Mobility, and Unemployment. This data is visualized through choropleths and bar charts. Additionally, a table view is included to give the user an easy tool when combing through the data.
import altair as alt
import pandas as pd
import numpy as np
from shapely import wkt
!pip install pipwin
!pip install panel
!pipwin install numpy
!pipwin install pandas
!pipwin install shapely
!pipwin install geopandas
import geopandas as gpd
import panel as pn
pn.extension('vega')
Requirement already satisfied: pipwin in c:\users\ericl\anaconda3\lib\site-packages (0.5.1) Requirement already satisfied: pySmartDL>=1.3.1; python_version >= "3.4" in c:\users\ericl\anaconda3\lib\site-packages (from pipwin) (1.3.4) Requirement already satisfied: js2py in c:\users\ericl\anaconda3\lib\site-packages (from pipwin) (0.70) Requirement already satisfied: pyprind in c:\users\ericl\anaconda3\lib\site-packages (from pipwin) (2.11.2) Requirement already satisfied: beautifulsoup4>=4.9.0 in c:\users\ericl\anaconda3\lib\site-packages (from pipwin) (4.9.3) Requirement already satisfied: requests in c:\users\ericl\anaconda3\lib\site-packages (from pipwin) (2.24.0) Requirement already satisfied: docopt in c:\users\ericl\anaconda3\lib\site-packages (from pipwin) (0.6.2) Requirement already satisfied: packaging in c:\users\ericl\anaconda3\lib\site-packages (from pipwin) (20.4) Requirement already satisfied: six in c:\users\ericl\anaconda3\lib\site-packages (from pipwin) (1.15.0) Requirement already satisfied: tzlocal>=1.2 in c:\users\ericl\anaconda3\lib\site-packages (from js2py->pipwin) (2.1) Requirement already satisfied: pyjsparser>=2.5.1 in c:\users\ericl\anaconda3\lib\site-packages (from js2py->pipwin) (2.7.1) Requirement already satisfied: soupsieve>1.2; python_version >= "3.0" in c:\users\ericl\anaconda3\lib\site-packages (from beautifulsoup4>=4.9.0->pipwin) (2.0.1) Requirement already satisfied: certifi>=2017.4.17 in c:\users\ericl\anaconda3\lib\site-packages (from requests->pipwin) (2020.6.20) Requirement already satisfied: chardet<4,>=3.0.2 in c:\users\ericl\anaconda3\lib\site-packages (from requests->pipwin) (3.0.4) Requirement already satisfied: urllib3!=1.25.0,!=1.25.1,<1.26,>=1.21.1 in c:\users\ericl\anaconda3\lib\site-packages (from requests->pipwin) (1.25.11) Requirement already satisfied: idna<3,>=2.5 in c:\users\ericl\anaconda3\lib\site-packages (from requests->pipwin) (2.10) Requirement already satisfied: pyparsing>=2.0.2 in c:\users\ericl\anaconda3\lib\site-packages (from packaging->pipwin) (2.4.7) Requirement already satisfied: pytz in c:\users\ericl\anaconda3\lib\site-packages (from tzlocal>=1.2->js2py->pipwin) (2020.1) Requirement already satisfied: panel in c:\users\ericl\anaconda3\lib\site-packages (0.11.3) Requirement already satisfied: markdown in c:\users\ericl\anaconda3\lib\site-packages (from panel) (3.3.4) Requirement already satisfied: bokeh<2.4.0,>=2.3.0 in c:\users\ericl\anaconda3\lib\site-packages (from panel) (2.3.1) Requirement already satisfied: requests in c:\users\ericl\anaconda3\lib\site-packages (from panel) (2.24.0) Requirement already satisfied: pyviz-comms>=0.7.4 in c:\users\ericl\anaconda3\lib\site-packages (from panel) (2.0.1) Requirement already satisfied: tqdm in c:\users\ericl\anaconda3\lib\site-packages (from panel) (4.50.2) Requirement already satisfied: pyct>=0.4.4 in c:\users\ericl\anaconda3\lib\site-packages (from panel) (0.4.8) Requirement already satisfied: param>=1.10.0 in c:\users\ericl\anaconda3\lib\site-packages (from panel) (1.10.1) Requirement already satisfied: tornado>=5.1 in c:\users\ericl\anaconda3\lib\site-packages (from bokeh<2.4.0,>=2.3.0->panel) (6.0.4) Requirement already satisfied: numpy>=1.11.3 in c:\users\ericl\anaconda3\lib\site-packages (from bokeh<2.4.0,>=2.3.0->panel) (1.20.1+mkl) Requirement already satisfied: PyYAML>=3.10 in c:\users\ericl\anaconda3\lib\site-packages (from bokeh<2.4.0,>=2.3.0->panel) (5.3.1) Requirement already satisfied: Jinja2>=2.7 in c:\users\ericl\anaconda3\lib\site-packages (from bokeh<2.4.0,>=2.3.0->panel) (2.11.2) Requirement already satisfied: python-dateutil>=2.1 in c:\users\ericl\anaconda3\lib\site-packages (from bokeh<2.4.0,>=2.3.0->panel) (2.8.1) Requirement already satisfied: pillow>=7.1.0 in c:\users\ericl\anaconda3\lib\site-packages (from bokeh<2.4.0,>=2.3.0->panel) (8.0.1) Requirement already satisfied: typing-extensions>=3.7.4 in c:\users\ericl\anaconda3\lib\site-packages (from bokeh<2.4.0,>=2.3.0->panel) (3.7.4.3) Requirement already satisfied: packaging>=16.8 in c:\users\ericl\anaconda3\lib\site-packages (from bokeh<2.4.0,>=2.3.0->panel) (20.4) Requirement already satisfied: chardet<4,>=3.0.2 in c:\users\ericl\anaconda3\lib\site-packages (from requests->panel) (3.0.4) Requirement already satisfied: certifi>=2017.4.17 in c:\users\ericl\anaconda3\lib\site-packages (from requests->panel) (2020.6.20) Requirement already satisfied: urllib3!=1.25.0,!=1.25.1,<1.26,>=1.21.1 in c:\users\ericl\anaconda3\lib\site-packages (from requests->panel) (1.25.11) Requirement already satisfied: idna<3,>=2.5 in c:\users\ericl\anaconda3\lib\site-packages (from requests->panel) (2.10) Requirement already satisfied: MarkupSafe>=0.23 in c:\users\ericl\anaconda3\lib\site-packages (from Jinja2>=2.7->bokeh<2.4.0,>=2.3.0->panel) (1.1.1) Requirement already satisfied: six>=1.5 in c:\users\ericl\anaconda3\lib\site-packages (from python-dateutil>=2.1->bokeh<2.4.0,>=2.3.0->panel) (1.15.0) Requirement already satisfied: pyparsing>=2.0.2 in c:\users\ericl\anaconda3\lib\site-packages (from packaging>=16.8->bokeh<2.4.0,>=2.3.0->panel) (2.4.7) Package `numpy` found in cache Downloading package . . . https://download.lfd.uci.edu/pythonlibs/w4tscw6k/numpy-1.20.1+mkl-cp38-cp38-win_amd64.whl numpy-1.20.1+mkl-cp38-cp38-win_amd64.whl
Traceback (most recent call last):
File "c:\users\ericl\anaconda3\lib\runpy.py", line 194, in _run_module_as_main
return _run_code(code, main_globals, None,
File "c:\users\ericl\anaconda3\lib\runpy.py", line 87, in _run_code
exec(code, run_globals)
File "C:\Users\ericl\anaconda3\Scripts\pipwin.exe\__main__.py", line 7, in <module>
File "c:\users\ericl\anaconda3\lib\site-packages\pipwin\command.py", line 103, in main
cache.install(package)
File "c:\users\ericl\anaconda3\lib\site-packages\pipwin\pipwin.py", line 300, in install
wheel_file = self.download(requirement)
File "c:\users\ericl\anaconda3\lib\site-packages\pipwin\pipwin.py", line 294, in download
return self._download(requirement, dest)
File "c:\users\ericl\anaconda3\lib\site-packages\pipwin\pipwin.py", line 290, in _download
obj.start()
File "c:\users\ericl\anaconda3\lib\site-packages\pySmartDL\pySmartDL.py", line 267, in start
urlObj = urllib.request.urlopen(req, timeout=self.timeout, context=self.context)
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 222, in urlopen
return opener.open(url, data, timeout)
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 531, in open
response = meth(req, response)
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 640, in http_response
response = self.parent.error(
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 569, in error
return self._call_chain(*args)
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 502, in _call_chain
result = func(*args)
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 649, in http_error_default
raise HTTPError(req.full_url, code, msg, hdrs, fp)
urllib.error.HTTPError: HTTP Error 404: Not Found
Package `pandas` found in cache Downloading package . . . https://download.lfd.uci.edu/pythonlibs/w4tscw6k/pandas-1.2.3-cp38-cp38-win_amd64.whl pandas-1.2.3-cp38-cp38-win_amd64.whl
Traceback (most recent call last):
File "c:\users\ericl\anaconda3\lib\runpy.py", line 194, in _run_module_as_main
return _run_code(code, main_globals, None,
File "c:\users\ericl\anaconda3\lib\runpy.py", line 87, in _run_code
exec(code, run_globals)
File "C:\Users\ericl\anaconda3\Scripts\pipwin.exe\__main__.py", line 7, in <module>
File "c:\users\ericl\anaconda3\lib\site-packages\pipwin\command.py", line 103, in main
cache.install(package)
File "c:\users\ericl\anaconda3\lib\site-packages\pipwin\pipwin.py", line 300, in install
wheel_file = self.download(requirement)
File "c:\users\ericl\anaconda3\lib\site-packages\pipwin\pipwin.py", line 294, in download
return self._download(requirement, dest)
File "c:\users\ericl\anaconda3\lib\site-packages\pipwin\pipwin.py", line 290, in _download
obj.start()
File "c:\users\ericl\anaconda3\lib\site-packages\pySmartDL\pySmartDL.py", line 267, in start
urlObj = urllib.request.urlopen(req, timeout=self.timeout, context=self.context)
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 222, in urlopen
return opener.open(url, data, timeout)
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 531, in open
response = meth(req, response)
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 640, in http_response
response = self.parent.error(
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 569, in error
return self._call_chain(*args)
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 502, in _call_chain
result = func(*args)
File "c:\users\ericl\anaconda3\lib\urllib\request.py", line 649, in http_error_default
raise HTTPError(req.full_url, code, msg, hdrs, fp)
urllib.error.HTTPError: HTTP Error 404: Not Found
Package `shapely` found in cache Downloading package . . . https://download.lfd.uci.edu/pythonlibs/w4tscw6k/Shapely-1.7.1-cp38-cp38-win_amd64.whl Shapely-1.7.1-cp38-cp38-win_amd64.whl [*] 0 bytes / 590 kB @ 0 bytes/s [------------------] [0.0%, 0s left] [*] 0 bytes / 590 kB @ 0 bytes/s [------------------] [0.0%, 0s left] [*] 0 bytes / 590 kB @ 0 bytes/s [------------------] [0.0%, 0s left] [*] 24 kB / 590 kB @ 60 kB/s [------------------] [4.1%, 0s left] [*] 88 kB / 590 kB @ 176 kB/s [##----------------] [14.9%, 0s left] [*] 200 kB / 590 kB @ 333 kB/s [######------------] [33.9%, 0s left] [*] 520 kB / 590 kB @ 743 kB/s [###############---] [88.2%, 0s left] Requirement already satisfied: Shapely==1.7.1 from file:///C:/Users/ericl/pipwin/Shapely-1.7.1-cp38-cp38-win_amd64.whl in c:\users\ericl\anaconda3\lib\site-packages (1.7.1) [*] 590 kB / 590 kB @ 743 kB/s [##################] [100%, 0s left] Package `geopandas` found in cache Downloading package . . . https://download.lfd.uci.edu/pythonlibs/w4tscw6k/geopandas-0.9.0-py3-none-any.whl geopandas-0.9.0-py3-none-any.whl [*] 0 bytes / 971 kB @ 0 bytes/s [------------------] [0.0%, 0s left] [*] 0 bytes / 971 kB @ 0 bytes/s [------------------] [0.0%, 0s left] [*] 0 bytes / 971 kB @ 0 bytes/s [------------------] [0.0%, 0s left] [*] 40 kB / 971 kB @ 100 kB/s [------------------] [4.1%, 0s left] [*] 168 kB / 971 kB @ 336 kB/s [###---------------] [17.3%, 0s left] [*] 344 kB / 971 kB @ 573 kB/s [######------------] [35.4%, 0s left] [*] 696 kB / 971 kB @ 994 kB/s [############------] [71.6%, 0s left] Requirement already satisfied: geopandas==0.9.0 from file:///C:/Users/ericl/pipwin/geopandas-0.9.0-py3-none-any.whl in c:\users\ericl\anaconda3\lib\site-packages (0.9.0) Requirement already satisfied: pyproj>=2.2.0 in c:\users\ericl\anaconda3\lib\site-packages (from geopandas==0.9.0) (3.0.1) Requirement already satisfied: shapely>=1.6 in c:\users\ericl\anaconda3\lib\site-packages (from geopandas==0.9.0) (1.7.1) Requirement already satisfied: pandas>=0.24.0 in c:\users\ericl\anaconda3\lib\site-packages (from geopandas==0.9.0) (1.2.3) Requirement already satisfied: fiona>=1.8 in c:\users\ericl\anaconda3\lib\site-packages (from geopandas==0.9.0) (1.8.18) Requirement already satisfied: certifi in c:\users\ericl\anaconda3\lib\site-packages (from pyproj>=2.2.0->geopandas==0.9.0) (2020.6.20) Requirement already satisfied: python-dateutil>=2.7.3 in c:\users\ericl\anaconda3\lib\site-packages (from pandas>=0.24.0->geopandas==0.9.0) (2.8.1) Requirement already satisfied: numpy>=1.16.5 in c:\users\ericl\anaconda3\lib\site-packages (from pandas>=0.24.0->geopandas==0.9.0) (1.20.1+mkl) Requirement already satisfied: pytz>=2017.3 in c:\users\ericl\anaconda3\lib\site-packages (from pandas>=0.24.0->geopandas==0.9.0) (2020.1) Requirement already satisfied: click<8,>=4.0 in c:\users\ericl\anaconda3\lib\site-packages (from fiona>=1.8->geopandas==0.9.0) (7.1.2) Requirement already satisfied: cligj>=0.5 in c:\users\ericl\anaconda3\lib\site-packages (from fiona>=1.8->geopandas==0.9.0) (0.7.1) Requirement already satisfied: six>=1.7 in c:\users\ericl\anaconda3\lib\site-packages (from fiona>=1.8->geopandas==0.9.0) (1.15.0) Requirement already satisfied: attrs>=17 in c:\users\ericl\anaconda3\lib\site-packages (from fiona>=1.8->geopandas==0.9.0) (20.3.0) Requirement already satisfied: munch in c:\users\ericl\anaconda3\lib\site-packages (from fiona>=1.8->geopandas==0.9.0) (2.5.0) Requirement already satisfied: click-plugins>=1.0 in c:\users\ericl\anaconda3\lib\site-packages (from fiona>=1.8->geopandas==0.9.0) (1.1.1) Requirement already satisfied: gdal~=3.2.1 in c:\users\ericl\anaconda3\lib\site-packages (from fiona>=1.8->geopandas==0.9.0) (3.2.2) [*] 971 kB / 971 kB @ 994 kB/s [##################] [100%, 0s left]
country_data = pd.read_csv('data_viz_final_project_data.csv')
country_data['geometry'] = country_data['geometry'].apply(wkt.loads)
country_data = gpd.GeoDataFrame(country_data, crs='epsg:4326')
continents = ['Africa', 'Asia', 'Europe', 'North America', 'South America', 'Oceania']
continent_radio = alt.binding_radio(options=continents)
continent_select = alt.selection_single(fields=['continent'], bind=continent_radio, name="continent")
continent_color_condition = alt.condition(continent_select,
alt.Color('continent:N', legend=None),
alt.value('lightgray'))
base = alt.Chart(country_data).mark_geoshape(invalid=None).encode(
color=alt.condition('datum.unemployment !== null', 'unemployment:Q', alt.value('lightgray')),
tooltip=['name', 'unemployment']
).project(type='albers').properties(
width=800,
height=600
).transform_filter(
continent_select
).project(
'equirectangular'
).properties(
width=500,
height=300
)
highlight_continent = base.add_selection(
continent_select
).encode(
color=continent_color_condition
).properties(title="Unemployment Choropleth")
filtered_une = country_data[pd.isna(country_data['unemployment']) == False]
bar = alt.Chart(filtered_une).mark_bar(invalid=None).encode(
y = alt.Y('unemployment:Q', axis=alt.Axis(format='%', title='Unemployment')),
x = alt.X('name', sort='-y'),
color = 'continent',
tooltip = ['name', 'unemployment']
).properties(title='Unemployment Bar Chart')
mean = alt.Chart(filtered_une).mark_rule(color='black', size=3).encode(
y='mean(unemployment):Q'
)
median = alt.Chart(filtered_une).mark_rule(color='gray', size=3).encode(
y='median(unemployment):Q'
)
unemployment_chart = highlight_continent + base | (bar + mean + median)
continents = ['Africa', 'Asia', 'Europe', 'North America', 'South America', 'Oceania']
continent_radio = alt.binding_radio(options=continents)
continent_select = alt.selection_single(fields=['continent'], bind=continent_radio, name="continent")
continent_color_condition = alt.condition(continent_select,
alt.Color('continent:N', legend=None),
alt.value('lightgray'))
base = alt.Chart(country_data).mark_geoshape(invalid=None).encode(
color=alt.condition('datum.newinflation !== null', 'newinflation:Q', alt.value('lightgray')),
tooltip=['name', 'inflation']
).project(type='albers').properties(
width=800,
height=600
).transform_filter(
continent_select
).project(
'equirectangular'
).properties(
width=500,
height=300
)
highlight_continent = base.add_selection(
continent_select
).encode(
color=continent_color_condition
).properties(title="Inflation Choropleth")
filtered_inf = country_data[pd.isna(country_data['inflation']) == False]
bar = alt.Chart(filtered_inf).mark_bar(invalid=None).encode(
y = alt.Y('inflation:Q', axis=alt.Axis(format='%', title='Inflation')),
x = alt.X('name', sort='-y'),
color = 'continent',
tooltip = ['name', 'inflation']
).properties(title='Inflation Bar Chart')
mean = alt.Chart(filtered_inf).mark_rule(color='black', size=3).encode(
y='mean(inflation):Q'
)
median = alt.Chart(filtered_inf).mark_rule(color='gray', size=3).encode(
y='median(inflation):Q'
)
inflation_chart = highlight_continent + base | (bar + mean + median)
continents = ['Africa', 'Asia', 'Europe', 'North America', 'South America', 'Oceania']
continent_radio = alt.binding_radio(options=continents)
continent_select = alt.selection_single(fields=['continent'], bind=continent_radio, name="continent")
continent_color_condition = alt.condition(continent_select,
alt.Color('continent:N', legend=None),
alt.value('lightgray'))
base = alt.Chart(country_data).mark_geoshape(invalid=None).encode(
color=alt.condition('datum.wage_gap !== null', 'wage_gap:Q', alt.value('lightgray')),
tooltip=['name', 'wage_gap']
).project(type='albers').properties(
width=800,
height=600
).transform_filter(
continent_select
).project(
'equirectangular'
).properties(
width=500,
height=300
)
highlight_continent = base.add_selection(
continent_select
).encode(
color=continent_color_condition
).properties(title="Wage Gap Choropleth")
filtered_wag = country_data[pd.isna(country_data['wage_gap']) == False]
bar = alt.Chart(filtered_wag).mark_bar(invalid=None).encode(
y = alt.Y('wage_gap:Q', axis=alt.Axis(format='%', title='Wage Gap')),
x = alt.X('name', sort='-y'),
color = 'continent',
tooltip = ['name', 'wage_gap']
).properties(title='Wage Gap Bar Chart')
mean = alt.Chart(filtered_wag).mark_rule(color='black', size=3).encode(
y='mean(wage_gap):Q'
)
median = alt.Chart(filtered_wag).mark_rule(color='gray', size=3).encode(
y='median(wage_gap):Q'
)
wage_gap_chart = highlight_continent + base | (bar + mean + median)
continents = ['Africa', 'Asia', 'Europe', 'North America', 'South America', 'Oceania']
continent_radio = alt.binding_radio(options=continents)
continent_select = alt.selection_single(fields=['continent'], bind=continent_radio, name="continent")
continent_color_condition = alt.condition(continent_select,
alt.Color('continent:N', legend=None),
alt.value('lightgray'))
base = alt.Chart(country_data).mark_geoshape(invalid=None).encode(
color=alt.condition('datum.social_mobility !== null', 'social_mobility:Q', alt.value('lightgray')),
tooltip=['name', 'social_mobility']
).project(type='albers').properties(
width=800,
height=600
).transform_filter(
continent_select
).project(
'equirectangular'
).properties(
width=500,
height=300
)
highlight_continent = base.add_selection(
continent_select
).encode(
color=continent_color_condition
).properties(title="Social Mobility Choropleth")
filtered_soc = country_data[pd.isna(country_data['social_mobility']) == False]
bar = alt.Chart(filtered_soc).mark_bar(invalid=None).encode(
y = alt.Y('social_mobility:Q', axis=alt.Axis(title='Social Mobility')),
x = alt.X('name', sort='-y'),
color = 'continent',
tooltip = ['name', 'social_mobility']
).properties(title='Social Mobility Bar Chart')
mean = alt.Chart(filtered_soc).mark_rule(color='black', size=3).encode(
y='mean(social_mobility):Q'
)
median = alt.Chart(filtered_soc).mark_rule(color='gray', size=3).encode(
y='median(social_mobility):Q'
)
social_mobility_chart = highlight_continent + base | (bar + mean + median)
continents = ['Africa', 'Asia', 'Europe', 'North America', 'South America', 'Oceania']
continent_radio = alt.binding_radio(options=continents)
continent_select = alt.selection_single(fields=['continent'], bind=continent_radio, name="continent")
continent_color_condition = alt.condition(continent_select,
alt.Color('continent:N', legend=None),
alt.value('lightgray'))
base = alt.Chart(country_data).mark_geoshape(invalid=None).encode(
color=alt.condition('datum.poverty !== null', 'poverty:Q', alt.value('lightgray')),
tooltip=['name', 'poverty']
).project(type='albers').properties(
width=800,
height=600
).transform_filter(
continent_select
).project(
'equirectangular'
).properties(
width=500,
height=300
)
highlight_continent = base.add_selection(
continent_select
).encode(
color=continent_color_condition
).properties(title="Poverty Choropleth")
filtered_pov = country_data[pd.isna(country_data['poverty']) == False]
bar = alt.Chart(filtered_pov).mark_bar(invalid=None).encode(
y = alt.Y('poverty:Q', axis=alt.Axis(format='%', title='Poverty')),
x = alt.X('name', sort='-y'),
color = 'continent',
tooltip = ['name', 'poverty']
).properties(title='Poverty Bar Chart')
mean = alt.Chart(filtered_pov).mark_rule(color='black', size=3).encode(
y='mean(poverty):Q'
)
median = alt.Chart(filtered_pov).mark_rule(color='gray', size=3).encode(
y='median(poverty):Q'
)
poverty_chart = highlight_continent + base | (bar + mean + median)
continents = ['Africa', 'Asia', 'Europe', 'North America', 'South America', 'Oceania']
continent_radio = alt.binding_radio(options=continents)
continent_select = alt.selection_single(fields=['continent'], bind=continent_radio, name="continent")
continent_color_condition = alt.condition(continent_select,
alt.Color('continent:N', legend=None),
alt.value('lightgray'))
base = alt.Chart(country_data).mark_geoshape(invalid=None).encode(
color=alt.condition('datum.inequality !== null', 'inequality:Q', alt.value('lightgray')),
tooltip=['name', 'inequality']
).project(type='albers').properties(
width=800,
height=600
).transform_filter(
continent_select
).project(
'equirectangular'
).properties(
width=500,
height=300
)
highlight_continent = base.add_selection(
continent_select
).encode(
color=continent_color_condition
).properties(title="Inequality Choropleth")
filtered_ine = country_data[pd.isna(country_data['inequality']) == False]
bar = alt.Chart(filtered_ine).mark_bar(invalid=None).encode(
y = alt.Y('inequality:Q', axis=alt.Axis(title='Inequality')),
x = alt.X('name', sort='-y'),
color = 'continent',
tooltip = ['name', 'inequality']
).properties(title='Inequality Bar Chart')
mean = alt.Chart(filtered_ine).mark_rule(color='black',size=3).encode(
y='mean(inequality):Q'
)
median = alt.Chart(filtered_ine).mark_rule(color='gray', size=3).encode(
y='median(inequality):Q'
)
inequality_chart = ((highlight_continent + base) | (bar + mean + median))
tabs = pn.Tabs()
tabs.append(('Wage Gap',wage_gap_chart))
tabs.append(('Unemployment', unemployment_chart))
tabs.append(('Social Mobility', social_mobility_chart))
tabs.append(('Inflation',inflation_chart))
tabs.append(('Poverty', poverty_chart))
tabs.append(('Inequality', inequality_chart))
tabs
from ipywidgets import widgets
from IPython.display import display
pd.set_option("display.max_rows", None, "display.max_columns", None)
table_data = country_data.copy()
table_data = table_data.drop(columns=['newinflation', 'geometry'])
#filter by country
def country_func(Country):
if Country=='All':
display(table_data)
else:
display(table_data[table_data['name'] == Country])
country_options = table_data['name'].tolist()
country_options.insert(0, 'All')
country_select = widgets.Select(options=country_options)
country_filter = widgets.interactive(country_func, Country=country_select)
#filter by continent
def cont_select(Continent):
if Continent=='All':
display(table_data)
else:
display(table_data[table_data['continent'] == Continent])
continent_options = ['All', 'Africa', 'Asia', 'Europe', 'North America', 'Oceania', 'South America']
continent_select = widgets.Select(options=continent_options)
continent_filter = widgets.interactive(cont_select, Continent=continent_select)
table = pn.Tabs()
table.append(('Filter by Country', country_filter))
table.append(('Filter by Continent', continent_filter))
table
full = pn.Tabs()
full.append(('Maps', tabs))
full.append(('Tables', table))
full
#filter by statistic with slider
stat_options = ['All', 'inflation', 'inequality', 'social_mobility', 'poverty', 'unemployment', 'wage_gap']
stat_slider = widgets.IntSlider(min=0, max=100, step=1, value=0)
stat_select = widgets.Select(options=stat_options)
def update_c_range(*args):
if stat_select.value=='All':
stat_slider.max = 100
else:
stat_slider.max = table_data[stat_select.value].max()
stat_slider.min = table_data[stat_select.value].min()
stat_slider.step = .01
stat_slider.value = 0
stat_select.observe(update_c_range, 'value')
def view3(Statistic, Slider):
if Statistic=='All':
display(table_data)
else:
display(table_data[table_data[Statistic] >= Slider])
widgets.interactive(view3,Statistic=stat_select,Slider=stat_slider)
--------------------------------------------------------------------------- TraitError Traceback (most recent call last) ~\anaconda3\lib\site-packages\ipywidgets\widgets\widget.py in _handle_msg(self, msg) 674 if 'buffer_paths' in data: 675 _put_buffers(state, data['buffer_paths'], msg['buffers']) --> 676 self.set_state(state) 677 678 # Handle a state request. ~\anaconda3\lib\site-packages\ipywidgets\widgets\widget.py in set_state(self, sync_data) 543 from_json = self.trait_metadata(name, 'from_json', 544 self._trait_from_json) --> 545 self.set_trait(name, from_json(sync_data[name], self)) 546 547 def send(self, content, buffers=None): ~\anaconda3\lib\contextlib.py in __exit__(self, type, value, traceback) 118 if type is None: 119 try: --> 120 next(self.gen) 121 except StopIteration: 122 return False ~\anaconda3\lib\site-packages\traitlets\traitlets.py in hold_trait_notifications(self) 1212 for changes in cache.values(): 1213 for change in changes: -> 1214 self.notify_change(change) 1215 1216 def _notify_trait(self, name, old_value, new_value): ~\anaconda3\lib\site-packages\ipywidgets\widgets\widget.py in notify_change(self, change) 604 # Send new state to front-end 605 self.send_state(key=name) --> 606 super(Widget, self).notify_change(change) 607 608 def __repr__(self): ~\anaconda3\lib\site-packages\traitlets\traitlets.py in notify_change(self, change) 1225 def notify_change(self, change): 1226 """Notify observers of a change event""" -> 1227 return self._notify_observers(change) 1228 1229 def _notify_observers(self, event): ~\anaconda3\lib\site-packages\traitlets\traitlets.py in _notify_observers(self, event) 1262 c = getattr(self, c.name) 1263 -> 1264 c(event) 1265 1266 def _add_notifiers(self, handler, name, type): ~\anaconda3\lib\site-packages\ipywidgets\widgets\widget_selection.py in _propagate_index(self, change) 233 self.label = label 234 if self.value is not value: --> 235 self.value = value 236 237 @validate('value') ~\anaconda3\lib\site-packages\traitlets\traitlets.py in __set__(self, obj, value) 602 raise TraitError('The "%s" trait is read-only.' % self.name) 603 else: --> 604 self.set(obj, value) 605 606 def _validate(self, obj, value): ~\anaconda3\lib\site-packages\traitlets\traitlets.py in set(self, obj, value) 591 # we explicitly compare silent to True just in case the equality 592 # comparison above returns something other than True/False --> 593 obj._notify_trait(self.name, old_value, new_value) 594 595 def __set__(self, obj, value): ~\anaconda3\lib\site-packages\traitlets\traitlets.py in _notify_trait(self, name, old_value, new_value) 1215 1216 def _notify_trait(self, name, old_value, new_value): -> 1217 self.notify_change(Bunch( 1218 name=name, 1219 old=old_value, ~\anaconda3\lib\site-packages\ipywidgets\widgets\widget.py in notify_change(self, change) 604 # Send new state to front-end 605 self.send_state(key=name) --> 606 super(Widget, self).notify_change(change) 607 608 def __repr__(self): ~\anaconda3\lib\site-packages\traitlets\traitlets.py in notify_change(self, change) 1225 def notify_change(self, change): 1226 """Notify observers of a change event""" -> 1227 return self._notify_observers(change) 1228 1229 def _notify_observers(self, event): ~\anaconda3\lib\site-packages\traitlets\traitlets.py in _notify_observers(self, event) 1262 c = getattr(self, c.name) 1263 -> 1264 c(event) 1265 1266 def _add_notifiers(self, handler, name, type): <ipython-input-201-03e33554b2e1> in update_c_range(*args) 9 stat_slider.max = 100 10 else: ---> 11 stat_slider.max = table_data[stat_select.value].max() 12 stat_slider.min = table_data[stat_select.value].min() 13 stat_slider.step = .01 ~\anaconda3\lib\site-packages\traitlets\traitlets.py in __set__(self, obj, value) 602 raise TraitError('The "%s" trait is read-only.' % self.name) 603 else: --> 604 self.set(obj, value) 605 606 def _validate(self, obj, value): ~\anaconda3\lib\site-packages\traitlets\traitlets.py in set(self, obj, value) 576 577 def set(self, obj, value): --> 578 new_value = self._validate(obj, value) 579 try: 580 old_value = obj._trait_values[self.name] ~\anaconda3\lib\site-packages\traitlets\traitlets.py in _validate(self, obj, value) 610 value = self.validate(obj, value) 611 if obj._cross_validation_lock is False: --> 612 value = self._cross_validate(obj, value) 613 return value 614 ~\anaconda3\lib\site-packages\traitlets\traitlets.py in _cross_validate(self, obj, value) 616 if self.name in obj._trait_validators: 617 proposal = Bunch({'trait': self, 'value': value, 'owner': obj}) --> 618 value = obj._trait_validators[self.name](obj, proposal) 619 elif hasattr(obj, '_%s_validate' % self.name): 620 meth_name = '_%s_validate' % self.name ~\anaconda3\lib\site-packages\traitlets\traitlets.py in __call__(self, *args, **kwargs) 973 """Pass `*args` and `**kwargs` to the handler's function if it exists.""" 974 if hasattr(self, 'func'): --> 975 return self.func(*args, **kwargs) 976 else: 977 return self._init_call(*args, **kwargs) ~\anaconda3\lib\site-packages\ipywidgets\widgets\widget_int.py in _validate_max(self, proposal) 116 max = proposal['value'] 117 if max < self.min: --> 118 raise TraitError('setting max < min') 119 if max < self.value: 120 self.value = max TraitError: setting max < min
select_country = widgets.Dropdown(
options=country_data['name'],
value='Afghanistan',
rows=len(country_data),
description='Country:'
)
selecter = display(select_country)
button_country = widgets.Button(description='Display DataFrame')
display(button_country)
def button_click(b, select_country):
display(country_data[country_data['name'] == select_country])
button_country.on_click(button_click(0, select_country.value))
| name | continent | inequality | wage_gap | social_mobility | poverty | newinflation | inflation | unemployment | geometry | |
|---|---|---|---|---|---|---|---|---|---|---|
| 0 | Afghanistan | Asia | NaN | NaN | NaN | NaN | 2.3 | 2.3 | 11.7 | POLYGON ((61.21082 35.65007, 62.23065 35.27066... |
sel = widgets.Dropdown(
options=['inflation', 'inequality', 'wage_gap', 'social_mobility', 'poverty', 'unemployment'],
value='inflation',
rows=6,
description='Statistic:'
)
display(sel)
button = widgets.Button(description='Display DataFrame')
display(button)
def button_click(b, sel):
display(country_data[['name', sel]])
button.on_click(button_click(0, sel.value))
| name | inflation | |
|---|---|---|
| 0 | Afghanistan | 2.3 |
| 1 | Albania | 1.4 |
| 2 | Algeria | 2.0 |
| 3 | Angola | 17.1 |
| 4 | Argentina | NaN |
| 5 | Armenia | 1.4 |
| 6 | Australia | 1.6 |
| 7 | Austria | 1.5 |
| 8 | Azerbaijan | 2.6 |
| 9 | Bahamas, The | 2.5 |
| 10 | Bangladesh | 5.6 |
| 11 | Belarus | 5.6 |
| 12 | Belgium | 1.4 |
| 13 | Belize | NaN |
| 14 | Benin | -0.9 |
| 15 | Bhutan | 2.7 |
| 16 | Bolivia | 1.8 |
| 17 | Bosnia and Herzegovina | 0.6 |
| 18 | Botswana | 2.8 |
| 19 | Brazil | 3.7 |
| 20 | Brunei | -0.4 |
| 21 | Bulgaria | 3.1 |
| 22 | Burkina Faso | 3.1 |
| 23 | Burundi | -0.7 |
| 24 | Cambodia | 2.5 |
| 25 | Cameroon | 2.5 |
| 26 | Canada | 1.9 |
| 27 | Central African Republic | NaN |
| 28 | Chad | -1.0 |
| 29 | Chile | 2.6 |
| 30 | China | 2.9 |
| 31 | Colombia | 3.5 |
| 32 | Costa Rica | 2.1 |
| 33 | Croatia | 0.8 |
| 34 | Cuba | NaN |
| 35 | Cyprus | 0.3 |
| 36 | Czech Republic | 2.8 |
| 37 | Democratic Republic of Congo | 2.9 |
| 38 | Denmark | 0.8 |
| 39 | Djibouti | 3.3 |
| 40 | Dominican Republic | 1.8 |
| 41 | Ecuador | 0.3 |
| 42 | Egypt | 14.4 |
| 43 | El Salvador | 0.1 |
| 44 | Equatorial Guinea | 1.2 |
| 45 | Eritrea | NaN |
| 46 | Estonia | 2.3 |
| 47 | Eswatini | 2.6 |
| 48 | Ethiopia | 15.8 |
| 49 | Fiji | 1.8 |
| 50 | Finland | 1.0 |
| 51 | France | 1.1 |
| 52 | Gabon | 2.5 |
| 53 | Gambia, The | 7.1 |
| 54 | Georgia | 4.9 |
| 55 | Germany | 1.4 |
| 56 | Ghana | 7.2 |
| 57 | Greece | 0.3 |
| 58 | Guatemala | 3.7 |
| 59 | Guinea | 9.5 |
| 60 | Guinea-Bissau | 0.2 |
| 61 | Guyana | 2.1 |
| 62 | Haiti | 18.7 |
| 63 | Honduras | 4.4 |
| 64 | Hungary | 3.3 |
| 65 | Iceland | 3.0 |
| 66 | India | 7.7 |
| 67 | Indonesia | 3.0 |
| 68 | Iran | 39.9 |
| 69 | Iraq | -0.2 |
| 70 | Ireland | 0.9 |
| 71 | Israel | 0.8 |
| 72 | Italy | 0.6 |
| 73 | Ivory Coast | -1.1 |
| 74 | Jamaica | 3.9 |
| 75 | Japan | 0.5 |
| 76 | Jordan | 0.8 |
| 77 | Kazakhstan | NaN |
| 78 | Kenya | 4.7 |
| 79 | Kosovo | 2.7 |
| 80 | Kuwait | 1.1 |
| 81 | Kyrgyzstan | 1.1 |
| 82 | Laos | 3.3 |
| 83 | Latvia | 2.8 |
| 84 | Lebanon | 3.0 |
| 85 | Lesotho | 5.2 |
| 86 | Liberia | 23.6 |
| 87 | Libya | 2.6 |
| 88 | Lithuania | 2.3 |
| 89 | Luxembourg | 1.7 |
| 90 | Madagascar | 5.6 |
| 91 | Malawi | 9.4 |
| 92 | Malaysia | 0.7 |
| 93 | Mali | -1.7 |
| 94 | Malta | 1.6 |
| 95 | Mauritania | 2.3 |
| 96 | Mexico | 3.6 |
| 97 | Moldova | 4.8 |
| 98 | Mongolia | 7.3 |
| 99 | Montenegro | 0.4 |
| 100 | Morocco | 0.2 |
| 101 | Mozambique | 2.8 |
| 102 | Myanmar | 8.8 |
| 103 | Namibia | 3.7 |
| 104 | Nepal | 5.6 |
| 105 | Netherlands | 2.6 |
| 106 | New Zealand | 1.6 |
| 107 | Nicaragua | 5.4 |
| 108 | Niger | -2.5 |
| 109 | Nigeria | 11.4 |
| 110 | North Macedonia | 0.8 |
| 111 | Norway | 2.2 |
| 112 | Oman | 0.1 |
| 113 | Pakistan | 10.6 |
| 114 | Panama | -0.4 |
| 115 | Papua New Guinea | 3.6 |
| 116 | Paraguay | 2.8 |
| 117 | Peru | 2.1 |
| 118 | Philippines | 2.5 |
| 119 | Poland | 2.2 |
| 120 | Portugal | 0.3 |
| 121 | Qatar | -0.7 |
| 122 | Republic of Congo | 2.2 |
| 123 | Romania | 3.8 |
| 124 | Russia | 4.5 |
| 125 | Rwanda | 3.3 |
| 126 | Saudi Arabia | -2.1 |
| 127 | Senegal | 1.8 |
| 128 | Serbia | 1.8 |
| 129 | Sierra Leone | 14.8 |
| 130 | Slovakia | 2.7 |
| 131 | Slovenia | 1.6 |
| 132 | Solomon Islands | 1.6 |
| 133 | Somalia | NaN |
| 134 | Somaliland | NaN |
| 135 | South Africa | 4.1 |
| 136 | South Korea | 0.4 |
| 137 | South Sudan | 187.9 |
| 138 | Spain | 0.7 |
| 139 | Sri Lanka | 3.5 |
| 140 | Sudan | 51.0 |
| 141 | Suriname | 22.0 |
| 142 | Sweden | 1.8 |
| 143 | Switzerland | 0.4 |
| 144 | Syria | 36.7 |
| 145 | Tajikistan | 6.0 |
| 146 | Tanzania | 3.4 |
| 147 | Thailand | 0.7 |
| 148 | Timor-Leste | 1.0 |
| 149 | Togo | 0.7 |
| 150 | Trinidad and Tobago | 1.0 |
| 151 | Tunisia | 6.7 |
| 152 | Turkey | 15.2 |
| 153 | Turkmenistan | NaN |
| 154 | Uganda | 2.9 |
| 155 | Ukraine | 7.9 |
| 156 | United Arab Emirates | -1.9 |
| 157 | United Kingdom | 1.7 |
| 158 | United States | 1.8 |
| 159 | Uruguay | 7.9 |
| 160 | Uzbekistan | NaN |
| 161 | Vanuatu | 2.8 |
| 162 | Venezuela | 254.9 |
| 163 | Vietnam | 2.8 |
| 164 | Yemen | 8.1 |
| 165 | Zambia | 9.2 |
| 166 | Zimbabwe | 10.6 |
continent = widgets.Dropdown(
options=['North America', 'South America', 'Europe', 'Africa', 'Asia', 'Oceania'],
value='North America',
rows=6,
description='Continent:'
)
display(continent)
button_cont = widgets.Button(description='Display DataFrame')
display(button)
def button_click(b, cont):
output = country_data[country_data['continent'] == cont]
output = output[['name', 'inequality', 'wage_gap', 'social_mobility', 'poverty', 'inflation', 'unemployment']]
display(output)
button_cont.on_click(button_click(0, continent.value))
| name | inequality | wage_gap | social_mobility | poverty | inflation | unemployment | |
|---|---|---|---|---|---|---|---|
| 9 | Bahamas, The | NaN | NaN | NaN | NaN | 2.5 | 14.4 |
| 13 | Belize | NaN | NaN | NaN | NaN | NaN | 7.8 |
| 26 | Canada | 0.303 | 17.594 | 76.1 | 0.118 | 1.9 | 9.5 |
| 32 | Costa Rica | 0.478 | 4.725 | 61.6 | 0.199 | 2.1 | 17.1 |
| 34 | Cuba | NaN | NaN | NaN | NaN | NaN | 3.9 |
| 40 | Dominican Republic | NaN | NaN | NaN | NaN | 1.8 | 8.9 |
| 43 | El Salvador | NaN | NaN | 47.4 | NaN | 0.1 | 7.0 |
| 58 | Guatemala | NaN | NaN | 43.5 | NaN | 3.7 | 4.7 |
| 62 | Haiti | NaN | NaN | NaN | NaN | 18.7 | 14.5 |
| 63 | Honduras | NaN | NaN | 43.5 | NaN | 4.4 | 9.4 |
| 74 | Jamaica | NaN | NaN | NaN | NaN | 3.9 | 8.4 |
| 96 | Mexico | 0.458 | 18.750 | 52.6 | 0.166 | 3.6 | 4.7 |
| 107 | Nicaragua | NaN | NaN | NaN | NaN | 5.4 | 5.8 |
| 114 | Panama | NaN | NaN | 51.4 | NaN | -0.4 | 10.2 |
| 158 | United States | 0.390 | 18.471 | 70.4 | 0.178 | 1.8 | 8.3 |